package cn.schoolwow.quickapi.module.business.api.flow.single;

import cn.schoolwow.quickapi.module.business.api.domain.API;
import cn.schoolwow.quickflow.domain.FlowContext;
import cn.schoolwow.quickflow.flow.BusinessFlow;
import org.springframework.web.bind.annotation.*;

import java.lang.annotation.Annotation;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;

public class GetByMethodMappingAnnotationFlow implements BusinessFlow {
    @Override
    public void executeBusinessFlow(FlowContext flowContext) throws Exception {
        setMappingClass(flowContext);
        setAPI(flowContext);
    }

    @Override
    public String name() {
        return "根据指定方法注解获取API信息";
    }

    private void setMappingClass(FlowContext flowContext){
        Method method = (Method) flowContext.checkData("method");

        Class[] mappingClasses = new Class[]{GetMapping.class, PostMapping.class, PutMapping.class, DeleteMapping.class, PatchMapping.class};
        for(Class mappingClass:mappingClasses) {
            Annotation annotation = method.getDeclaredAnnotation(mappingClass);
            if (annotation == null) {
                continue;
            }
            flowContext.putCurrentFlowData("mappingClass", mappingClass);
            flowContext.putCurrentFlowData("annotation", annotation);
            return;
        }
        flowContext.brokenCurrentFlow("不存在指定Mapping注解类");
    }

    private void setAPI(FlowContext flowContext) throws NoSuchMethodException, InvocationTargetException, IllegalAccessException {
        Class mappingClass = (Class) flowContext.checkData("mappingClass");
        Annotation annotation = (Annotation) flowContext.checkData("annotation");
        API api = (API) flowContext.checkData("api");

        String requestMethod = mappingClass.getSimpleName().substring(0,mappingClass.getSimpleName().lastIndexOf("Mapping")).toUpperCase();
        api.requestMethod = requestMethod.toUpperCase();
        String[] values = (String[]) mappingClass.getDeclaredMethod("value").invoke(annotation);
        if(values.length>0){
            api.url = values[0];
        }else{
            api.url = "";
        }
    }
}
